package com.zbkj.crmeb.store.service.impl;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Objects;

import javax.annotation.Resource;

import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.zbkj.crmeb.system.model.SystemAdmin;
import com.zbkj.crmeb.system.service.SystemAdminService;
import com.zbkj.crmeb.user.model.User;
import com.zbkj.crmeb.user.service.UserService;
import lombok.extern.slf4j.Slf4j;
import org.redisson.Redisson;
import org.redisson.api.RLock;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;

import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.crmeb.core.exception.CrmebException;
import com.zbkj.crmeb.enums.HomeStyleEnum;
import com.zbkj.crmeb.store.dao.HomeStyleDao;
import com.zbkj.crmeb.store.dto.HomeStyleDTO;
import com.zbkj.crmeb.store.model.HomeStyle;
import com.zbkj.crmeb.store.service.HomeStyleService;

@Service
@Slf4j
public class HomeStyleServiceImpl extends ServiceImpl<HomeStyleDao, HomeStyle> implements HomeStyleService {
    @Resource
    private HomeStyleDao homeStyleDao;

    @Resource
    private Redisson redisson;

    @Resource
    private UserService userService;

    @Resource
    private SystemAdminService systemAdminService;

    private final static String STYLE_KEY = "STYLE_KEY_";

    @Override
    public List<HomeStyleDTO> listEntity(Integer merId) {
        List<HomeStyle> list = this.list(Wrappers.<HomeStyle>lambdaQuery()
                .eq(HomeStyle :: getMerId, merId)
                .isNull(HomeStyle :: getActivityId)
                .orderByAsc(HomeStyle :: getSort)
                );
        // 对象复制
        List<HomeStyleDTO> homeStyleDTO = new ArrayList<>();
        for(HomeStyle homeStyle : list) {
            HomeStyleDTO dto = new HomeStyleDTO();
            BeanUtils.copyProperties(homeStyle, dto);
            if (null == dto.getVersion()){
                dto.setVersion(1);
            }
            dto.setType(homeStyle.getType().getValue());
            dto.setPosition(JSON.parseObject(homeStyle.getPosition()));
            dto.setParame(JSON.parseObject(homeStyle.getParame()));
            dto.setStyle(JSON.parseObject(homeStyle.getStyle()));
            homeStyleDTO.add(dto);
        }
        
        return homeStyleDTO;
    }

    @Override
    public List<HomeStyleDTO> listEntityByType(Integer merId, Integer type) {
        List<HomeStyle> list = this.list(Wrappers.<HomeStyle>lambdaQuery()
                .eq(HomeStyle :: getMerId, merId)
                .eq(HomeStyle :: getType, type)
                .isNull(HomeStyle :: getActivityId)
                .orderByAsc(HomeStyle :: getSort)
                )
        ;
        // 对象复制
        List<HomeStyleDTO> homeStyleDTO = new ArrayList<>();
        for(HomeStyle homeStyle : list) {
            HomeStyleDTO dto = new HomeStyleDTO();
            BeanUtils.copyProperties(homeStyle, dto);
            if (null == dto.getVersion()){
                dto.setVersion(1);
            }
            dto.setType(homeStyle.getType().getValue());
            dto.setPosition(JSON.parseObject(homeStyle.getPosition()));
            dto.setParame(JSON.parseObject(homeStyle.getParame()));
            dto.setStyle(JSON.parseObject(homeStyle.getStyle()));
            homeStyleDTO.add(dto);
        }
        
        return homeStyleDTO;
    }
    
    @Override
    public List<HomeStyleDTO> listEntityByActivityId(Integer id) {
    	List<HomeStyle> list = this.list(Wrappers.<HomeStyle>lambdaQuery()
    			.eq(HomeStyle :: getActivityId, id)
    			.eq(HomeStyle :: getIsShow, true)
    			.orderByAsc(HomeStyle :: getSort)
    			)
    			;
    	// 对象复制
    	List<HomeStyleDTO> homeStyleDTO = new ArrayList<>();
    	for(HomeStyle homeStyle : list) {
    		HomeStyleDTO dto = new HomeStyleDTO();
    		BeanUtils.copyProperties(homeStyle, dto);
            if (null == dto.getVersion()){
                dto.setVersion(1);
            }
    		dto.setType(homeStyle.getType().getValue());
    		dto.setPosition(JSON.parseObject(homeStyle.getPosition()));
    		dto.setParame(JSON.parseObject(homeStyle.getParame()));
    		dto.setStyle(JSON.parseObject(homeStyle.getStyle()));
    		homeStyleDTO.add(dto);
    	}
    	
    	return homeStyleDTO;
    }

    @Override
    public Boolean saveEntity(Integer merId, List<HomeStyleDTO> homeStyleDTOs) {
        List<HomeStyle> homeStyles = new ArrayList<>();
        SystemAdmin systemAdmin = systemAdminService.getInfo();
        long operateTime = System.currentTimeMillis();
        for (HomeStyleDTO homeStyle : homeStyleDTOs) {
            log.info("保存{}装修模板，当前操作人: {},操作时间: {},保存内容: {}",merId,systemAdmin.getAccount(),operateTime,JSON.toJSONString(homeStyle));
        }

        RLock rLock = redisson.getLock(STYLE_KEY+merId);
        try {
            if (!rLock.tryLock()) {
                throw new CrmebException("其他人正在使用，请刷新页面后重新修改并提交,当前操作人: "+systemAdmin.getAccount());
            }
            HomeStyleDTO homeStyleDTO = homeStyleDTOs.get(0);
            // 校验版本号
//            checkStyleVersion(merId,homeStyleDTO);
            for(int i=0; i<homeStyleDTOs.size(); i++) {
                if(null == homeStyleDTOs.get(i).getType()) {
                    throw new CrmebException("类型不能为空");
                }
                // 版本号+1
                if (null != homeStyleDTOs.get(i).getVersion()){
                    homeStyleDTOs.get(i).setVersion(homeStyleDTOs.get(i).getVersion() +1);
                }
                // 对象赋值
                homeStyleDTOs.get(i).setMerId(merId);
                HomeStyle homeStyle = new HomeStyle();
                BeanUtils.copyProperties(homeStyleDTOs.get(i), homeStyle);
                homeStyle.setSort(i);
                homeStyle.setType(HomeStyleEnum.valueOf(homeStyleDTOs.get(i).getType()));
                homeStyle.setPosition(homeStyleDTOs.get(i).getPosition().toJSONString());
                if (null!=homeStyleDTOs.get(i).getParame()){
                    homeStyle.setParame(homeStyleDTOs.get(i).getParame().toJSONString());
                }
                homeStyle.setStyle(homeStyleDTOs.get(i).getStyle().toJSONString());
                if(null == homeStyle.getId()) {
                    homeStyle.setCreateTime(new Date());
                } else {
                    HomeStyle homeStyleDB = this.getOne(Wrappers.<HomeStyle>lambdaQuery()
                            .eq(HomeStyle :: getMerId, merId)
                            .eq(HomeStyle :: getId, homeStyleDTOs.get(i).getId())
                            .last("LIMIT 1")
                    );
                    if(null == homeStyleDB) {
                        throw new CrmebException("记录不存在");
                    }
                }
                homeStyle.setUpdateTime(new Date());
                homeStyles.add(homeStyle);
            }
            return this.saveOrUpdateBatch(homeStyles);
        }catch (Exception e){
            log.error("装修模板保存失败:",e);
            rLock.unlock();
        }finally {
            rLock.unlock();
        }
        return false;
    }

    private void checkStyleVersion(Integer merId,HomeStyleDTO homeStyleDTO) {
        if (null == homeStyleDTO || homeStyleDTO.getVersion() == null || homeStyleDTO.getVersion() == 0){
            return;
        }
        List<HomeStyle> list = this.list(Wrappers.<HomeStyle>lambdaQuery()
                .eq(HomeStyle :: getMerId, merId)
                .isNull(HomeStyle :: getActivityId)
                .orderByAsc(HomeStyle :: getSort)
        );
        // 不存在数据
        if (CollectionUtils.isEmpty(list)){
            return;
        }
        HomeStyle homeStyle = list.get(0);
        if (Objects.equals(homeStyle.getVersion(),homeStyleDTO.getVersion())){
            throw new CrmebException("装修模板已被人更新，请刷新后重新提交");
        }
        // 版本号+1
        homeStyleDTO.setVersion(homeStyleDTO.getVersion()+1);

    }

    @Override
    public Boolean deleteActivityStyle(Integer activityId) {
        return this.remove(Wrappers.<HomeStyle>lambdaQuery()
                .eq(HomeStyle::getActivityId, activityId));
    }

}
